#include"stdio.h"
#include"os_type.h"
#include"asm_utils.h"

STDIO::STDIO()
{
    initialize();
}
void STDIO::initialize()
{
    screen = (uint8*)0xb8000;
}
void STDIO::print(uint x,uint y,uint8 c,uint8 color)
{
    if(x >= 25 || y >= 80)
    {
        return;
    }
    uint pos = x*80+y;
    screen[2*pos]=c;
    screen[2*pos+1]=color;
}
void STDIO::print(uint8 c,uint8 color)
{
    uint cursor=getCursor();
    screen[2*cursor]=c;
    screen[2*cursor+1]=color;
    cursor++;
    if (cursor==25*80)
    {
        rollUp();
        cursor=24*80;
    }
    moveCursor(cursor);
}
void STDIO::print(uint8 c)
{
    print(c,0x07);
}
void STDIO::moveCursor(uint position)
{
    if(position>=80*25)
    {
        return;
    }
    uint8 temp;
    //处理高8位
    temp=(position>>8)&0xff;
    asm_out_port(0x3d4,0x0e);
    asm_out_port(0x3d5,temp);
    //处理低8位
    temp=position & 0xff;
    asm_out_port(0x3d4,0x0f);
    asm_out_port(0x3d5,temp);
}
void STDIO::moveCursor(uint x,uint y)
{
    if(x>=25 || y>=80)
    {
        return;
    }
    moveCursor(x*80+y);
}
uint STDIO::getCursor()
{
    uint pos=0;
    uint8 temp=0;
    //处理高8位
    asm_out_port(0x3d4,0x0e);
    asm_in_port(0x3d5,&temp);
    pos=((uint)temp)<<8;
    //处理低8位
    asm_out_port(0x3d4,0x0f);
    asm_in_port(0x3d5,&temp);
    pos=pos | ((uint)temp);
    return pos;
}
void STDIO::rollUp()
{
    uint length;
    length=25*80;
    for(uint i=80; i<length; i++)
    {
        screen[2*(i-80)]=screen[2*i];
        screen[2*(i-80)+1]=screen[2*i+1];
    }
    for(uint i=24*80; i<length;i++)
    {
        screen[2*i]=' ';
        screen[2*i+1]=0x07;
    }
}